package com.blacktry.entity.easypoidata;

import com.alibaba.excel.context.AnalysisContext;
import com.alibaba.excel.event.AnalysisEventListener;
import com.alibaba.excel.metadata.BaseRowModel;
import com.baomidou.mybatisplus.core.conditions.Wrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.blacktry.entity.model.CourseDistribution;
import com.blacktry.entity.model.Course;
import com.blacktry.service.CourseDistributionService;
import com.blacktry.service.impl.CourseDistributionServiceImpl;
import com.blacktry.service.impl.CourseServiceImpl;
import com.blacktry.utils.GetBeanUtil;
import lombok.extern.slf4j.Slf4j;
import org.apache.ibatis.session.SqlSession;
import org.apache.pdfbox.jbig2.util.log.Logger;
import org.apache.pdfbox.jbig2.util.log.LoggerFactory;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Slf4j
public class CourseListener<T extends BaseRowModel> extends AnalysisEventListener<Course> {

    private static final Logger LOGGER = LoggerFactory.getLogger(com.blacktry.entity.easypoidata.DemoDataListener.class);
    /**
     * 每隔5条存储数据库，实际使用中可以3000条，然后清理list ，方便内存回收
     */
    private static final int BATCH_COUNT = 20;
    List<Course> list = new ArrayList<Course>();
    List<CourseDistribution> courseDistributionList = new ArrayList<CourseDistribution>();
    CourseDistributionServiceImpl courseDistributionService = new CourseDistributionServiceImpl();

    /**
     * 这个每一条数据解析都会来调用
     *
     * @param data    one row value. Is is same as {@link AnalysisContext#readRowHolder()}
     * @param context
     */
    @Override
    public void invoke(Course data, AnalysisContext context) {
        // 课程分配表初始状态依据于任务预处理表
        CourseDistribution courseDistribution = new CourseDistribution();
        // 如果队列里面有就更新队列的，队列里没有看数据库有没有，有的话更新数据库，否则加入队列
        boolean flag = false;// 不在队列标志
        if (data.getCourseId() != null) {
 /**
  * 自动注入有问题，无法实时清洗数据
  * System.out.println("解析到一条数据->" + data);
            for (int i = 0; i < list.size(); i++) {
                if (list.get(i).getCourseId().equals(data.getCourseId())) {
                    list.get(i).setCourseId(list.get(i).getCourseId() + "," + data.getCourseId());
                    flag = true;
                    break;
                }
            }
            QueryWrapper<CourseDistribution> wrapper = new QueryWrapper<>();
            wrapper.lambda().eq(CourseDistribution::getCourseId,data.getCourseId());
//            CourseDistribution inDataBase = courseDistributionService.getOne(wrapper);
            CourseDistribution inDataBase = courseDistributionService.selectByCourseId(data.getCourseId());
            if (!flag &&null == inDataBase) {// 不在队列 不再数据库 就加入到队列里
                this.list.add(data);
            } else {// 在数据库
                inDataBase.setCourseId(data.getCourseId());
                courseDistributionService.updateById(inDataBase);
            }
        **/

            this.list.add(data);
            // 课程分配表数据填充,放入默认班级对课程的关联关系
            courseDistribution.setClassId(data.getClassNum());
            courseDistribution.setCourseId(data.getCourseId());
            courseDistributionList.add(courseDistribution);

            // 对于课程时长周次的切割
            if (data.getTimeWeekNum() != null) {
                String[] timeWeekNum = data.getTimeWeekNum().split("/");
                data.setTimeWeek(Integer.valueOf(timeWeekNum[0]));
                data.setWeekNum(timeWeekNum[1]);
            }

            if (this.list.size() >= BATCH_COUNT) {
                saveData(this.list);
                // 存储完成清理 list
                this.list.clear();
                courseDistributionList.clear();
            }
        }
//         达到BATCH_COUNT了，需要去存储一次数据库，防止数据几万条数据在内存，容易OOM
    }

    /**
     * 所有数据解析完成了 都会来调用
     *
     * @param context
     */
    @Override
    public void doAfterAllAnalysed(AnalysisContext context) {
        // 这里也要保存数据，确保最后遗留的数据也存储到数据库
        saveData(list);
        LOGGER.info("所有数据解析完成！");
    }

    /**
     * 加上存储数据库
     */
    private void saveData(List<Course> list) {
        LOGGER.info("开始存储数据库！");
        CourseServiceImpl courseService = new CourseServiceImpl();
        courseService.saveOrUpdateBatch(list);
//        list.forEach(System.out::println);
        courseDistributionService.saveOrUpdateBatch(courseDistributionList);
        LOGGER.info("存储数据库成功！");
    }
}
